home *** CD-ROM | disk | FTP | other *** search
-
-
-
- xxxxttttaaaallllkkkk____ppppiiiioooo((((DDDD3333)))) xxxxttttaaaallllkkkk____ppppiiiioooo((((DDDD3333))))
-
-
-
- NNNNAAAAMMMMEEEE
- _xxxx_tttt_aaaa_llll_kkkk______pppp_iiii_oooo______aaaa_dddd_dddd_rrrr - construct PIO address
- _xxxx_tttt_aaaa_llll_kkkk______pppp_iiii_oooo_tttt_rrrr_aaaa_nnnn_ssss______aaaa_dddd_dddd_rrrr - construct PIO address
- _xxxx_tttt_aaaa_llll_kkkk______pppp_iiii_oooo_mmmm_aaaa_pppp______aaaa_llll_llll_oooo_cccc - allocate an XIO PIO channel
- _xxxx_tttt_aaaa_llll_kkkk______pppp_iiii_oooo_mmmm_aaaa_pppp______aaaa_dddd_dddd_rrrr - set PIO channel target
- _xxxx_tttt_aaaa_llll_kkkk______pppp_iiii_oooo_mmmm_aaaa_pppp______dddd_oooo_nnnn_eeee - mark PIO channel unused
- _xxxx_tttt_aaaa_llll_kkkk______pppp_iiii_oooo_mmmm_aaaa_pppp______ffff_rrrr_eeee_eeee - release XIO PIO channel resources
-
- SSSSYYYYNNNNOOOOPPPPSSSSIIIISSSS
- #include <sys/XIO/xtalk.h>
-
- caddr_t
- xtalk_pio_addr(vertex_hdl_t _v_h_d_l,
- device_desc_t _d_e_s_c,
- iopaddr_t _a_d_d_r,
- size_t _s_i_z_e,
- xtalk_piomap_t *_m_a_p_p,
- unsigned _f_l_a_g_s)
-
- caddr_t
- xtalk_piotrans_addr(vertex_hdl_t _v_h_d_l,
- device_desc_t _d_e_s_c,
- iopaddr_t _a_d_d_r,
- size_t _s_i_z_e,
- unsigned _f_l_a_g_s)
-
- xtalk_piomap_t
- xtalk_piomap_alloc(vertex_hdl_t _v_h_d_l,
- device_desc_t _d_e_s_c,
- iopaddr_t _a_d_d_r,
- size_t _s_i_z_e,
- size_t _m_a_x,
- unsigned _f_l_a_g_s)
-
- caddr_t
- xtalk_piomap_addr(xtalk_piomap_t _m_a_p,
- iopaddr_t addr,
- size_t size);
-
- void
- xtalk_piomap_done(xtalk_piomap_t _x_t_a_l_k__p_i_o_m_a_p)
-
- void
- xtalk_piomap_free(xtalk_piomap_t _x_t_a_l_k__p_i_o_m_a_p)
-
-
- AAAArrrrgggguuuummmmeeeennnnttttssss
- _v_h_d_l is the appropriate XIO connection point.
-
- _d_e_s_c is a device descriptor, usually zero.
-
-
-
-
-
- PPPPaaaaggggeeee 1111
-
-
-
-
-
-
- xxxxttttaaaallllkkkk____ppppiiiioooo((((DDDD3333)))) xxxxttttaaaallllkkkk____ppppiiiioooo((((DDDD3333))))
-
-
-
- _a_d_d_r is the XIO address on the target device.
-
- _s_i_z_e is the size of the mapped region.
-
- _a_l_i_g_n is a desired alignment.
-
- _m_a_x is the maximum size mapped at any one time.
-
- _f_l_a_g_s is reserved and should be zero.
-
- _m_a_p is the result of a previous xtalk_piomap_alloc call.
-
- _m_a_p_p is a place to record a map that may be allocated.
-
-
- DDDDEEEESSSSCCCCRRRRIIIIPPPPTTTTIIIIOOOONNNN
- When a device driver wishes to use Programmed I/O (PIO) to communicate
- with a device, the system needs to have a chance to set up any
- appropriate mapping registers.
-
- There are two different models for how to do this. The simple model
- provides permanent mappings through fixed mapping resources.
-
- +o _x_t_a_l_k__p_i_o_t_r_a_n_s__a_d_d_r() is generally called at device attach time to
- construct a permanent address that can be used for PIO access to a
- device's control registers; it attempts to use shared resources to
- construct a physical address that, when used, will route transactions
- to the proper target on the XIO bus. This is not always possible,
- and when it is not, the function will return NULL.
-
- +o _x_t_a_l_k__p_i_o__a_d_d_r() is a wrapper function that calls
- _x_t_a_l_k__p_i_o_t_r_a_n_s__a_d_d_r() to establish a mapping, and if that fails, it
- then allocates a piomap using _x_t_a_l_k__p_i_o_m_a_p__a_l_l_o_c() and fills it in
- using _x_t_a_l_k__p_i_o_m_a_p__a_d_d_r(), returning the resulting piomap via the map
- pointer _m_a_p_p.
-
- It is not always possible to establish such mappings using common shared
- system resources, so the concept of a PIO channel that preallocates
- scarce mapping resources is provided.
-
- Such channels are allocated using _x_t_a_l_k__p_i_o_m_a_p__a_l_l_o_c(), which is given
- the limits of the region that will be mapped, and the maximum size to be
- mapped from within that region.
-
- +o _x_t_a_l_k__p_i_o_m_a_p__a_d_d_r() is then used to actually establish the proper
- mappings for a PIO target; given the address and the size of the
- region for PIO, it will hand back the base address to be used for
- accessing that region.
-
- +o If the same PIO channel is to be used at different times to map
- different target areas, _x_t_a_l_k__p_i_o_m_a_p__d_o_n_e() should be called to idle
- any mapping hardware (and possibly flush out any pipes or buffers
-
-
-
- PPPPaaaaggggeeee 2222
-
-
-
-
-
-
- xxxxttttaaaallllkkkk____ppppiiiioooo((((DDDD3333)))) xxxxttttaaaallllkkkk____ppppiiiioooo((((DDDD3333))))
-
-
-
- along the path that might do unexpected things when mapping registers
- are modified). Then _x_t_a_l_k__p_i_o_m_a_p__a_d_d_r() can again be called,
- specifying the new target area.
-
- When a driver is completely finished with a PIO channel -- either because
- the channel is used only for initialization of the device, or because the
- device or the driver is being shut down -- the PIO channel resources
- should be released back to the system using _x_t_a_l_k__p_i_o_m_a_p__f_r_e_e().
-
-
- EEEEXXXXAAAAMMMMPPPPLLLLEEEESSSS
- Here is a contrived example of how one might initialize a very strange
- XIO card. It is not clear that this would be the best way to do it, but
- it does give an example of the relationship between the various
- functions.
-
- xiofoo_attach(vertex_hdl_t vhdl)
- {
- unsigned *cfgspace;
- struct xiofoo_devregs *devregs;
- xtalk_piomap_t pmap;
- xtalk_piomap_t cmap;
- struct xiofoo_chan_config *tune;
-
- ...
-
- /* Get a pointer we can use for PIO to our
- * device's control registers. This call
- * is blindly assuming that a "piotrans"
- * to the base of a widget will always work,
- * which we would like to be true but may
- * not be able to always guarantee.
- */
- devregs = xtalk_piotrans_addr(
- vhdl, 0,
- 0, sizeof (struct xiofoo_devregs),
- 0);
-
- if (cfgspace == NULL) {
- cmn_err(CE_ALERT,
- "xiofoo_attach: xtalk_piotrans_addr failed");
- return -1;
- }
-
- ...
-
- /* pretend our "channel" space is too big
- * to successfully map with piotrans, so
- * we have to use piomap, and that it is
- * too big for us to get it in one call
- * to piomap_addr.
- *
-
-
-
- PPPPaaaaggggeeee 3333
-
-
-
-
-
-
- xxxxttttaaaallllkkkk____ppppiiiioooo((((DDDD3333)))) xxxxttttaaaallllkkkk____ppppiiiioooo((((DDDD3333))))
-
-
-
- * This would be the case, for instance,
- * if the board took its 48 bits of address
- * space, divided it into 16 equal pieces,
- * and assigned each one to a logical portion
- * of its task: on some large systems, we
- * just can't keep fixed shared mapping
- * resources set up for all 48 bits of all
- * the widgets in the system.
- */
-
- cmap = xtalk_piomap_alloc(vhdl, 0,
- CHAN_OFFSET, CHAN_SEP * CHANS,
- sizeof (struct xiofoo_chan_config), 0);
-
- for (chan = 0; chan < chans; ++chan) {
- tune = (struct xiofoo_chan_config *)
- xtalk_piomap_addr(cmap, CHAN_SEP * chan,
- sizeof (struct xiofoo_chan_config));
-
- /* now fiddle with this particular channel */
- tune->chan = chan + 2;
- tune->volume = 5;
- tune->balance = 0;
-
- xtalk_piomap_done(cmap);
- }
- xtalk_piomap_free(cmap);
- ...
- }
-
-
- NNNNOOOOTTTTEEEESSSS
- It is not necessary to separately establish mappings for each individual
- PIO target register; it is more efficient to use a single mapping to
- cover an entire device register set.
-
-
-
- SSSSEEEEEEEE AAAALLLLSSSSOOOO
- xtalk(D3), xtalk_dma(D3), xtalk_error(D3), xtalk_get(D3), xtalk_intr(D3).
-
-
- DDDDIIIIAAAAGGGGNNNNOOOOSSSSTTTTIIIICCCCSSSS
- _x_t_a_l_k__p_i_o_t_r_a_n_s__a_d_d_r() will return a null pointer if shared (fixed)
- resources can not be used to construct a valid physical address that maps
- to the desired range of XIO addresses.
-
- _x_t_a_l_k__p_i_o_m_a_p__a_l_l_o_c() will return a null pointer if resources can not be
- allocated to establish PIO mappings to the described region, or if the
- parameters are inconsistent.
-
-
-
-
-
- PPPPaaaaggggeeee 4444
-
-
-
-
-
-
- xxxxttttaaaallllkkkk____ppppiiiioooo((((DDDD3333)))) xxxxttttaaaallllkkkk____ppppiiiioooo((((DDDD3333))))
-
-
-
- _x_t_a_l_k__p_i_o_m_a_p__a_d_d_r() will return a null pointer if the specified target
- address can not be mapped using the specified PIO channel; this would
- usually be due to specifying a target block that is outside the
- previously specified target area or is larger than the previously
- specified maximum mapping size. It may also return a null pointer if the
- PIO channel is currently in use and has not been marked idle by a
- _x_t_a_l_k__p_i_o_m_a_p__d_o_n_e() call.
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
- PPPPaaaaggggeeee 5555
-
-
-
-